#pragma once
#ifndef __AI_Agent_h_
#define __AI_Agent_h_

#include "OgreBulletDynamics.h"
#include <OIS/OIS.h>
#include "Ogre.h"
#include "AI_Manager.h"

class AI_Agent
{
public:
	int mID;
	int currWaypointIndex;
	AI_Agent(int id, AI_TrackPath *trackPath, Ogre::SceneManager*, OgreBulletDynamics::DynamicsWorld*, Ogre::Vector3 kartPosition,
		     std::vector<TimingGate> *gates, Real *raceTime);
	~AI_Agent();
	void steerKart(float dir); //Specifies which direction to turn the steering wheel.
	void accelerateOrBrake(float dir); //Specifies how much throttle or break is being applied.
	bool update(Ogre::Real elapsedTime, GameState state);
	Ogre::Vector3 getForwardVector();
	Ogre::Real getVelocity();
	void attachSoundtoEngine(String soundName, OgreOggSound::OgreOggSoundManager *soundMngr);
	int getID();
	int getCurrentLap();
	int getLastTimingGate();
	Real getLastTimingGateTime();

private:
	Ogre::SceneManager* mSceneMgr;
	OgreBulletDynamics::DynamicsWorld *mWorld;
	GameState mGameState;
	std::vector<TimingGate> *mTimingGates;
	Real *mRaceTime;
	int mCurrLap;
	std::vector<Real> mLastTimeAtTimingGate;
	int mNextGate;

	OgreBulletDynamics::WheeledRigidBody	*mCarChassis;
	OgreBulletDynamics::VehicleTuning		*mTuning;
	OgreBulletDynamics::VehicleRayCaster	*mVehicleRayCaster;
	OgreBulletDynamics::RaycastVehicle		*mVehicle;

	Ogre::Entity    *mChassis;
	Ogre::Entity    *mSteeringWheel;
	Ogre::Entity    *mWheels[4];
	Ogre::SceneNode *mChassisNode;
	Ogre::SceneNode *mSteeringWheelNode;
	Ogre::SceneNode *mWheelNodes[4];
	Ogre::SceneNode *mEngineNode;

	int mWheelsEngine[4];
	int mWheelsEngineCount;
	int mWheelsSteerable[4];
	int mWheelsSteerableCount;
	float mEngineForce;
	float mBrakeForce;
	float mSteering;
	float mSteeringTarget;
	int mWheelEngineStyle;
	int mWheelSteeringStyle;
	bool mSteeringLeft;
	bool mSteeringRight;

	AI_TrackPath *mTrackPath;
	Vector3 mPrevLocation;
	Real mStuckTimer;

	bool createKart(Ogre::Vector3 kartPosition);
	void incWaypointIndex();
	void setSteeringToNextWaypoint();
	void setThrottleToNextWaypoint();
	Real checkDistanceToNextWaypoint();
	float calculateSteeting();
	void incNextGate();
	float DistanceToNextTimingGate();
	void updateGateTimers();
	bool checkIfStuck();
	void applyUnstuckImpulse();
};

#endif // #ifndef __AI_Agent_h_